package com.example.demo.ecrypt;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONException;
import com.alibaba.fastjson.JSONObject;
import com.alibaba.fastjson.support.config.FastJsonConfig;
import com.alibaba.fastjson.support.spring.FastJsonHttpMessageConverter;
import com.example.demo.util.ConvertUtil;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpInputMessage;
import org.springframework.http.HttpOutputMessage;
import org.springframework.http.MediaType;
import org.springframework.http.converter.HttpMessageNotReadableException;
import org.springframework.http.converter.HttpMessageNotWritableException;

import java.io.*;
import java.lang.reflect.Type;
import java.nio.charset.StandardCharsets;
import java.util.Base64;

public class EncryptMessageConverter extends FastJsonHttpMessageConverter {

    private static final MediaType cjcEncrypt = new MediaType("application", "cjcenc");

    private Object readType(Type type, String data) throws IOException {
        try {
            FastJsonConfig fastJsonConfig = getFastJsonConfig();
            return JSON.parseObject(new ByteArrayInputStream(data.getBytes(StandardCharsets.UTF_8)), fastJsonConfig.getCharset(), type, fastJsonConfig.getFeatures());
        } catch (JSONException ex) {
            throw new HttpMessageNotReadableException("JSON parse error: " + ex.getMessage(), ex);
        } catch (IOException ex) {
            throw new HttpMessageNotReadableException("I/O error while reading input message", ex);
        }
    }

    @Override
    public Object read(Type type, Class<?> contextClass, HttpInputMessage inputMessage) throws IOException, HttpMessageNotReadableException {
        if (cjcEncrypt.isCompatibleWith(inputMessage.getHeaders().getContentType())) {
            String data = ConvertUtil.inputStream2String(inputMessage.getBody());
//            System.out.println(data);
            byte[] decode = Base64.getDecoder().decode(data.getBytes("utf8"));
            String s = new String(decode);
//            System.out.println(s);
            return readType(getType(type, contextClass), s);
        }
//        return null;
        return super.read(type, contextClass, inputMessage);
    }

    @Override
    public void write(Object o, Type type, MediaType contentType, HttpOutputMessage outputMessage) throws IOException, HttpMessageNotWritableException {
//        OutputStream body = outputMessage.getBody();
//        System.out.println(outputMessage.getBody().toString());
//        super.write(o, type, contentType, outputMessage);



        if (!cjcEncrypt.isCompatibleWith(contentType)) {
            super.write(o, type, contentType, outputMessage);
            return;
        }
        OutputStream body = outputMessage.getBody();
//        HttpHeaders headers = outputMessage.getHeaders();
//        System.out.println(contentType);
//        System.out.println(headers);
//        headers.setContentType(contentType);
//        headers.setContentType(cjcEncrypt);
//        System.out.println(JSONObject.toJSON(o));

//        body.write("sossoosoosososos".getBytes("utf8"));
        body.write(Base64.getEncoder().encode(JSONObject.toJSON(o).toString().getBytes("utf8")));

    }
}
